# To change this template, choose Tools | Templates
# and open the template in the editor.

module Shapefile

  require 'geo_ruby'
  require 'geo_ruby/shp4r/shp'
  require 'geo_ruby/geojson'

  # Creates a Shapefile for the aggregate Noisetube maps
  # parameter:
  #   filename_str = filename as a string without file extension
  #
  # Additional fields can be added here. Arguments: Column_name, data_type, size
  # Keep in mind: Shapefiles have a limitation
  def self.create_shapefile(filename_str)
    # .prj file 4326: GEOGCS["GCS_WGS_1984",DATUM["D_WGS_1984",SPHEROID["WGS_1984",6378137,298.257223563]],PRIMEM["Greenwich",0],UNIT["Degree",0.017453292519943295]]
    prj_file = File.new("#{filename_str}.prj", "w")
    prj_file.puts('GEOGCS["GCS_WGS_1984",DATUM["D_WGS_1984",SPHEROID["WGS_1984",6378137,298.257223563]],PRIMEM["Greenwich",0],UNIT["Degree",0.017453292519943295]]')
    prj_file.close
    GeoRuby::Shp4r::ShpFile.create(
      "#{filename_str}.shp",   
      GeoRuby::Shp4r::ShpType::POLYGON,
      [ GeoRuby::Shp4r::Dbf::Field.new("meandb","N",3),
        GeoRuby::Shp4r::Dbf::Field.new("mindb","N",3),
        GeoRuby::Shp4r::Dbf::Field.new("maxdb","N",3),
        GeoRuby::Shp4r::Dbf::Field.new("meas_size","N", 10),
        GeoRuby::Shp4r::Dbf::Field.new("start_time","C", 10),
        GeoRuby::Shp4r::Dbf::Field.new("end_time","C", 10)
      ] )
  end


  # Add a polygon to the shapefile by providing the polygon as a geojson string
  # parameters:
  #   shpfile = a shapefile, created with 'create_shapefile'
  #   polygon_geojson = a geojson snippet (e.g. { "type": "Polygon", ... } )
  #   avgdb, etc. : integers
  def self.write_geojson_to_shapefile(shpfile, polygon_geojson, meandb, mindb, maxdb, measures_size)
    shpfile.transaction do |tr|
      tr.add(GeoRuby::Shp4r::ShpRecord.new(
        GeoRuby::SimpleFeatures::Polygon.from_geojson(polygon_geojson),
        'meandb' => meandb,
        'mindb' => mindb,
        'maxdb' => maxdb,
        'meas_size' => measures_size))
    end
  end


  # Add a polygon to the shapefile by providing the polygon as a WKT string
  # parameters:
  #   shpfile = a shapefile, created with 'create_shapefile'
  #   polygon_WKT = a WKT representation of a polygon
  #   avgdb, etc. : integers
  def self.write_wkt_to_shapefile(shpfile, polygon_wkt, meandb, mindb, maxdb, measures_size)
    shpfile.transaction do |tr|
      tr.add(GeoRuby::Shp4r::ShpRecord.new(
        GeoRuby::SimpleFeatures::Polygon.from_ewkt(polygon_wkt),
        'meandb' => meandb,
        'mindb' => mindb,
        'maxdb' => maxdb,
        'meas_size' => measures_size))
    end
  end
  # shpfile.close not mandatory?

  
   def self.write_array_to_shapefile(shpfile, array, start_time, end_time)
    shpfile.transaction do |tr|
      array.each {|grid_element|
        if grid_element[:count] > 0
         polygon_wkt = bounding_box_to_wkt(grid_element[:xmax], grid_element[:ymin],grid_element[:xmin] , grid_element[:ymax])
         tr.add(
           GeoRuby::Shp4r::ShpRecord.new(
            GeoRuby::SimpleFeatures::Polygon.from_ewkt(polygon_wkt),
           'meandb' => grid_element[:mean],
           'mindb' => grid_element[:mindb],
           'maxdb' => grid_element[:maxdb],
           'meas_size' => grid_element[:count],
           'start_time' => start_time,
           'end_time' => end_time))
        end
      }
    end
   end

  def self.zip_shapefiles(file_name)

    #files
    input_filenames = ["#{file_name}.dbf", "#{file_name}.shp", "#{file_name}.shx"]

    #zip file name will always be same name
    zipfile_name = SHAPE_FILES_PATH + file_name + ".zip"

    Zip::File.open(zipfile_name, Zip::File::CREATE) do |zipfile|

      input_filenames.each do |filename|
        # Two arguments:
        # - The name of the file as it will appear in the archive
        # - The original file, including the path to find it
        zipfile.add(filename, SHAPE_FILES_PATH + filename)
      end
    end

    zipfile_name
  end


  
  # Generates a POLYGON WKT from a given grid element that is specified by the top left and bottom right corner.
  # BTW:  x = long, y = lat
  def self.bounding_box_to_wkt(tl_lat, tl_lng, br_lat, br_lng)
    "POLYGON((#{tl_lng} #{br_lat}, #{tl_lng} #{tl_lat}, #{br_lng} #{tl_lat}, #{br_lng} #{br_lat}, #{tl_lng} #{br_lat}))"
  end



  def self.create_filename_for_map(map)
     "#{map.name.gsub!(/ /, '_') || map.name}_noise_#{map.start_time.strftime('%Y%m%d')}_#{map.end_time.strftime('%Y%m%d')}"
  end

  def self.get_folder_for_map(map)
    split = map.name.upcase.split('_', 3)
    if split[0] == split[1] # case Baia_Baia_Train_station , no subarea = 2x pilot name
     "#{split[0]}"
     else
      "#{split[0]}/#{split[1]}" # case PILOT/SUBAREA
    end
  end

end

